﻿using System;
using System.Collections.Generic;
using System.Linq;
using System.Text;
using System.Threading;
using System.Collections;

namespace DARE
{
    /// <summary>
    /// Helper to made an Enumerable class
    /// </summary>
    /// <typeparam name="T">T</typeparam>
    public abstract class CEnumeratorHelper<T> : IEnumerable<T>, IEnumerator<T>
    {
        #region Fields
        
        private Dictionary<Thread, int> m_enumerat;
        protected T m_current;
        
        #endregion


        #region Property

        /// <summary>
        /// 
        /// </summary>
        object IEnumerator.Current
        {
            get { return this.m_current; }
        }

        /// <summary>
        /// 
        /// </summary>
        public T Current
        {
            get { return this.m_current; }
        }
        
        #endregion

        #region CTOR

        /// <summary>
        /// 
        /// </summary>
        public CEnumeratorHelper()
        {
            m_enumerat = new Dictionary<Thread, int>();
        }

        #endregion

        #region Method

        /// <summary>
        /// 
        /// </summary>
        /// <returns></returns>
        public IEnumerator<T> GetEnumerator()
        {
            return this;
        }

        /// <summary>
        /// 
        /// </summary>
        /// <returns></returns>
        IEnumerator IEnumerable.GetEnumerator()
        {
            return this;
        }

        /// <summary>
        /// 
        /// </summary>
        /// <returns></returns>
        public virtual bool MoveNext()
        {
            Thread _current = Thread.CurrentThread;
            lock (this.m_enumerat)
            {
                if (!this.m_enumerat.ContainsKey(_current))
                    this.m_enumerat.Add(_current, 0);
            }
            int i = this.m_enumerat[_current];
            bool resp = ValidateEnumerator(i);
            if (resp)
            {
                this.m_enumerat[_current] = ++i;
                return true;
            }
            return false;
        }

        /// <summary>
        /// 
        /// </summary>
        public void Reset()
        {
            throw new NotImplementedException();
        }

        /// <summary>
        /// 
        /// </summary>
        public void Dispose()
        {
            Thread _current = Thread.CurrentThread;
            lock (this.m_enumerat)
            {
                if (this.m_enumerat.ContainsKey(_current))
                    this.m_enumerat.Remove(_current);
            }
        }

        /// <summary>
        /// 
        /// </summary>
        /// <param name="index"></param>
        /// <returns></returns>
        protected abstract bool ValidateEnumerator(int index);

        #endregion
    }
}
